home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
C/C++ Users Group Library 1996 July
/
C-C++ Users Group Library July 1996.iso
/
vol_200
/
204_01
/
getsym.c
< prev
next >
Wrap
Text File
|
1980-01-01
|
18KB
|
555 lines
#include <stdio.h>
#include "c.h"
#include "expr.h"
#include "gen.h"
#include "cglbdec.h"
/*
* 68000 C compiler
*
* Copyright 1984, 1985, 1986 Matthew Brandt.
* all commercial rights reserved.
*
* This compiler is intended as an instructive tool for personal use. Any
* use for profit without the written consent of the author is prohibited.
*
* This compiler may be distributed freely for non-commercial use as long
* as this notice stays intact. Please forward any enhancements or questions
* to:
*
* Matthew Brandt
* Box 920337
* Norcross, Ga 30092
*/
static int errno[80];
static int numerrs;
static char inline[132];
int total_errors = 0;
char *lptr; /* shared with preproc */
FILE *inclfile[10]; /* shared with preproc */
int inclline[10]; /* shared with preproc */
int incldepth; /* shared with preproc */
char *linstack[20]; /* stack for substitutions */
char chstack[20]; /* place to save lastch */
int lstackptr = 0; /* substitution stack pointer */
int isalnum(c)
char c;
{ return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') ||
(c >= '0' && c <= '9');
}
int isidch(c)
char c;
{ return isalnum(c) || c == '_' || c == '$';
}
int isspace(c)
char c;
{ return c == ' ' || c == '\t' || c == '\n';
}
int isdigit(c)
char c;
{ return (c >= '0' && c <= '9');
}
initsym()
{ lptr = inline;
inline[0] = 0;
numerrs = 0;
total_errors = 0;
lineno = 0;
}
int getline(listflag)
int listflag;
{ int rv;
if( lineno > 0 && listflag) {
fprintf(list,"%6d\t%s",lineno,inline);
while(numerrs--)
fprintf(list," *** error %d\n",errno[numerrs]);
numerrs = 0;
}
++lineno;
rv = (fgets(inline,131,input) == NULL);
if( rv && incldepth > 0 ) {
fclose(input);
input = inclfile[--incldepth];
lineno = inclline[incldepth];
return getline(0);
}
if( rv )
return 1;
lptr = inline;
if(inline[0] == '#')
return preprocess();
return 0;
}
/*
* getch - basic get character routine.
*/
int getch()
{ while( (lastch = *lptr++) == '\0') {
if( lstackptr > 0 ) {
lptr = linstack[--lstackptr];
lastch = chstack[lstackptr];
return lastch;
}
if(getline(incldepth == 0))
return lastch = -1;
}
return lastch;
}
/*
* error - print error information
*/
error(n)
int n;
{ errno[numerrs++] = n;
++total_errors;
}
/*
* getid - get an identifier.
*
* identifiers are any isidch conglomerate
* that doesn't start with a numeric character.
* this set INCLUDES keywords.
*/
int getid()
{ register int i;
i = 0;
while(isidch(lastch)) {
if(i < 19)
lastid[i++] = lastch;
getch();
}
lastid[i] = '\0';
lastst = id;
}
/*
* getsch - get a character in a quoted string.
*
* this routine handles all of the escape mechanisms
* for characters in strings and character constants.
*/
int getsch() /* return an in-quote character */
{ register int i, j;
if(lastch == '\n')
return -1;
if(lastch != '\\') {
i = lastch;
getch();
return i;
}
getch(); /* get an escaped character */
if(isdigit(lastch)) {
i = 0;
for(i = 0;j < 3;++j) {
if(lastch <= '7' && lastch >= '0')
i = (i << 3) + lastch - '0';
else
break;
getch();
}
return i;
}
i = lastch;
getch();
switch(i) {
case '\n':
getch();
return getsch();
case 'b':
return '\b';
case 'f':
return '\f';
case 'n':
return '\n';
case 'r':
return '\r';
case 't':
return '\t';
default:
return i;
}
}
int radix36(c)
char c;
{ if(isdigit(c))
return c - '0';
if(c >= 'a' && c <= 'z')
return c - 'a' + 10;
if(c >= 'A' && c <= 'Z')
return c - 'A' + 10;
return -1;
}
/*
* getbase - get an integer in any base.
*/
getbase(b)
{ register int i, j;
i = 0;
while(isalnum(lastch)) {
if((j = radix36(lastch)) < b) {
i = i * b + j;
getch();
}
else break;
}
ival = i;
lastst = iconst;
}
/*
* getfrac - get fraction part of a floating number.
*/
getfrac()
{ double frmul;
frmul = 0.1;
while(isdigit(lastch)) {
rval += frmul * (lastch - '0');
getch();
frmul *= 0.1;
}
}
/*
* getexp - get exponent part of floating number.
*
* this algorithm is primative but usefull. Floating
* exponents are limited to +/-255 but most hardware
* won't support more anyway.
*/
getexp()
{ double expo, exmul;
expo = 1.0;
if(lastst != rconst)
rval = ival;
if(lastch = '-') {
exmul = 0.1;
getch();
}
else
exmul = 10.0;
getbase(10);
if(ival > 255)
error(ERR_FPCON);
else
while(ival--)
expo *= exmul;
rval *= expo;
}
/*
* getnum - get a number from input.
*
* getnum handles all of the numeric input. it accepts
* decimal, octal, hexidecimal, and floating point numbers.
*/
getnum()
{ register int i, j, k;
i = 0;
if(lastch == '0') {
getch();
if(lastch == 'x' || lastch == 'X') {
getch();
getbase(16);
}
else getbase(8);
}
else {
getbase(10);
if(lastch == '.') {
getch();
rval = ival; /* float the integer part */
getfrac(); /* add the fractional part */
lastst = rconst;
}
if(lastch == 'e' || lastch == 'E') {
getch();
getexp(); /* get the exponent */
}
}
}
/*
* getsym - get next symbol from input stream.
*
* getsym is the basic lexical analyzer. It builds
* basic tokens out of the characters on the input
* stream and sets the following global variables:
*
* lastch: A look behind buffer.
* lastst: type of last symbol read.
* laststr: last string constant read.
* lastid: last identifier read.
* ival: last integer constant read.
* rval: last